package com.rickpan.service;

import com.rickpan.entity.ProjectAnnouncement;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;

import java.time.LocalDateTime;
import java.util.List;
import java.util.Optional;

/**
 * 项目公告服务接口
 * 
 * @author RickPan Team
 * @since 2024-01-15
 */
public interface ProjectAnnouncementService {

    /**
     * 创建公告
     */
    ProjectAnnouncement createAnnouncement(ProjectAnnouncement announcement);

    /**
     * 更新公告
     */
    ProjectAnnouncement updateAnnouncement(ProjectAnnouncement announcement);

    /**
     * 删除公告
     */
    void deleteAnnouncement(Long announcementId);

    /**
     * 根据ID查找公告
     */
    Optional<ProjectAnnouncement> findById(Long announcementId);

    /**
     * 根据项目ID查找公告列表
     */
    List<ProjectAnnouncement> findAnnouncementsByProject(Long projectId);

    /**
     * 根据项目ID查找公告列表（分页）
     */
    Page<ProjectAnnouncement> findAnnouncementsByProject(Long projectId, Pageable pageable);

    /**
     * 根据项目ID查找置顶公告
     */
    List<ProjectAnnouncement> findPinnedAnnouncementsByProject(Long projectId);

    /**
     * 根据项目ID查找非置顶公告
     */
    List<ProjectAnnouncement> findNormalAnnouncementsByProject(Long projectId);

    /**
     * 根据项目ID查找非置顶公告（分页）
     */
    Page<ProjectAnnouncement> findNormalAnnouncementsByProject(Long projectId, Pageable pageable);

    /**
     * 根据创建者ID查找公告列表
     */
    List<ProjectAnnouncement> findAnnouncementsByCreator(Long creatorId);

    /**
     * 搜索公告
     */
    List<ProjectAnnouncement> searchAnnouncements(Long projectId, String keyword);

    /**
     * 搜索公告（分页）
     */
    Page<ProjectAnnouncement> searchAnnouncements(Long projectId, String keyword, Pageable pageable);

    /**
     * 根据时间范围查找公告
     */
    List<ProjectAnnouncement> findAnnouncementsByDateRange(Long projectId, LocalDateTime startDate, LocalDateTime endDate);

    /**
     * 根据时间范围查找公告（分页）
     */
    Page<ProjectAnnouncement> findAnnouncementsByDateRange(Long projectId, LocalDateTime startDate, LocalDateTime endDate, Pageable pageable);

    /**
     * 查找今日公告
     */
    List<ProjectAnnouncement> findTodayAnnouncements(Long projectId);

    /**
     * 查找本周公告
     */
    List<ProjectAnnouncement> findWeekAnnouncements(Long projectId);

    /**
     * 查找本月公告
     */
    List<ProjectAnnouncement> findMonthAnnouncements(Long projectId);

    /**
     * 置顶公告
     */
    void pinAnnouncement(Long announcementId);

    /**
     * 取消置顶公告
     */
    void unpinAnnouncement(Long announcementId);

    /**
     * 获取公告统计信息
     */
    AnnouncementStatistics getAnnouncementStatistics(Long projectId);

    /**
     * 检查用户是否有公告管理权限
     */
    boolean hasAnnouncementManagePermission(Long announcementId, Long userId);

    /**
     * 检查用户是否有公告查看权限
     */
    boolean hasAnnouncementViewPermission(Long announcementId, Long userId);

    /**
     * 公告统计信息类
     */
    class AnnouncementStatistics {
        private long totalAnnouncements;
        private long pinnedAnnouncements;
        private long todayAnnouncements;
        private long weekAnnouncements;
        private long monthAnnouncements;

        // 构造函数
        public AnnouncementStatistics() {}

        public AnnouncementStatistics(long totalAnnouncements, long pinnedAnnouncements, 
                                    long todayAnnouncements, long weekAnnouncements, long monthAnnouncements) {
            this.totalAnnouncements = totalAnnouncements;
            this.pinnedAnnouncements = pinnedAnnouncements;
            this.todayAnnouncements = todayAnnouncements;
            this.weekAnnouncements = weekAnnouncements;
            this.monthAnnouncements = monthAnnouncements;
        }

        // Getter 和 Setter
        public long getTotalAnnouncements() { return totalAnnouncements; }
        public void setTotalAnnouncements(long totalAnnouncements) { this.totalAnnouncements = totalAnnouncements; }

        public long getPinnedAnnouncements() { return pinnedAnnouncements; }
        public void setPinnedAnnouncements(long pinnedAnnouncements) { this.pinnedAnnouncements = pinnedAnnouncements; }

        public long getTodayAnnouncements() { return todayAnnouncements; }
        public void setTodayAnnouncements(long todayAnnouncements) { this.todayAnnouncements = todayAnnouncements; }

        public long getWeekAnnouncements() { return weekAnnouncements; }
        public void setWeekAnnouncements(long weekAnnouncements) { this.weekAnnouncements = weekAnnouncements; }

        public long getMonthAnnouncements() { return monthAnnouncements; }
        public void setMonthAnnouncements(long monthAnnouncements) { this.monthAnnouncements = monthAnnouncements; }
    }
}
